﻿using System;
using System.Collections;
using System.Diagnostics;
using System.IO;
using System.Net;
using System.Reflection;
using System.Text.RegularExpressions;
using System.Threading;
using System.Xml;
using InfoJetSoft.Service.Entity;
using InfoJetSoft.Service.Util;
using Microsoft.SharePoint;

namespace InfoJetSoft.Service.Worker
{
    /// <summary>
    /// 负责想WebDav服务器(SharePoint)提交表单数据.
    /// </summary>
    class DataObjectDavSubmitWorker
    {
        //使用给定DavAdapter提交表单
        public static void submitDoc(Form form, DataDavAdapter davAdapter)
        {
            //先查找给定DavAdapter是否有匹配的loginConnection,可能没有,没有就是null.
            UnauthorizedConnection loginConnection = DataWebUnauthorizedWorker.findLoginConnection(form, davAdapter);
            submitDoc(form, davAdapter, loginConnection);
        }

        //使用给定DavAdapter和loginConnection提交表单
        public static void submitDoc(Form form, DataDavAdapter davAdapter, UnauthorizedConnection loginConnection)
        {
            //先确定文件名.
            string filePath = null;
            string fileName = davAdapter.FileName;
            if (fileName == null)
            {
                fileName = getFileName(form, davAdapter);
            }
            if (fileName == null)
            {
                fileName = "Form.xml";
            }
            //如果文件名中包含:,替换为_.
            fileName = fileName.Replace(":", "_");
            fileName = StringUtil.formatUrl(fileName);

            //CID 1304 //2012.09.06 //Begin
            string folderUrl = davAdapter.FolderURLValue;
            if (form.JetContext.RelativeUrlResolver != null)
            {
                folderUrl = form.JetContext.RelativeUrlResolver.resolve(folderUrl);
            }
            //保证davAdapter.FolderURLValue以\或/结尾.
            if ((folderUrl.EndsWith("/") || folderUrl.EndsWith("\\")))
            {
                filePath = folderUrl + fileName;
            }
            else
            {
                filePath = folderUrl + "/" + fileName;
            }
            //FileLog.log("----------------Submit form start------------------");
            //FileLog.log("Get FolderUrl:"+folderUrl);
            //FileLog.log("Get FilePath:"+filePath);
            //CID 1304 //2012.09.06 //End
            //try
            //{
                Uri uri = new Uri(filePath);
                ICredentials credentials = DataWebUnauthorizedWorker.getCredentialCache(form.HttpContext, uri, loginConnection);
            //}
            //catch (Exception mm)
            //{
            //    throw new InfoJetException("[Path]" + filePath, null);
            //}
            //CID 0370 //2009.07.17 //Begin
            
            //CID 0370 //2009.07.17 //End

            //Modified by lishuchao 2013.6.25
            using (SPSite site = new SPSite(folderUrl))
            {
                using (SPWeb web = site.OpenWeb())
                {
                    web.AllowUnsafeUpdates = true;
                    //FileLog.log("Got Site:[SiteUrl]"+site.Url);
                    //FileLog.log("Got Web:[WebUrl]"+web.Url);
                    //test by sunny 2013.12
                    //throw new InfoJetException("[siteUrl]" + site.Url + "[webUrl]" + web.Url + "[folderUrl]" + folderUrl + "[Path]" + filePath, null);
                    //FileLog.log("Geting File: [FilePath]"+filePath);
                    try
                    {
                        SPFile file = web.GetFile(filePath);
                        //FileLog.log("File Exist:" + file.Exists);
                        if (file.Exists && (!davAdapter.OverwriteAllowed))
                        {
                            //FileLog.log("File Exists and OverWriteForbidden");
                            //FileLog.log("----------------Submit form end------------------");
                            //test by sunny 2013.12
                            //throw new InfoJetException("File has existed.", null);
                            throw new InfoJetException(MessageUtil.DavFormExisted(uri), null);
                        }
                    }
                    catch (Exception ex)
                    {
                        
                        if (ex.Message == MessageUtil.DavFormExisted(uri))
                        {
                            throw new InfoJetException(MessageUtil.DavFormExisted(uri), null);
                        }
                      //  FileLog.log("error occored:" + ex.ToString());
                        
                    }
                    //FileLog.log("Geting Folder:[FolderUrl]"+folderUrl);
                    SPFolder folder = web.GetFolder(folderUrl);
                    //FileLog.log("GotFolder");
                    //将XmlDoc去掉JetId,后转化为byte数组.
                    JetIdCache idCache = new JetIdCache(form.XmlDoc.DocumentElement);
                    byte[] content = System.Text.UTF8Encoding.UTF8.GetBytes(DOMUtil.toString(form.XmlDoc));
                    idCache.reset();

                    //FileLog.log("Adding File: [fileName]" + fileName + "[OverwriteAllowed]" + davAdapter.OverwriteAllowed);
                    
                    SPFile newFile = folder.Files.Add(fileName, content, davAdapter.OverwriteAllowed);
                    //FileLog.log("File Updated");
                    web.AllowUnsafeUpdates = false;
                    //FileLog.log("----------------Submit form end------------------");
                }
            }


            //先判断文件是否存在,及DavAdapter定义中是否可以覆盖文件.
            //if (existForm(uri, credentials) && (!davAdapter.OverwriteAllowed))
            //{
            //    //CID 0859 //2012.03.20 //Begin
            //    throw new InfoJetException(MessageUtil.DavFormExisted(uri), null);
            //    //CID 0859 //2012.03.20 //End
            //}

            ////将XmlDoc去掉JetId,后转化为byte数组.
            ////JetIdCache idCache = new JetIdCache(form.XmlDoc.DocumentElement);
            ////byte[] content = System.Text.UTF8Encoding.UTF8.GetBytes(DOMUtil.toString(form.XmlDoc));
            ////idCache.reset();

            ////使用HTTP提交.
            //HttpWebRequest request = (HttpWebRequest)WebRequest.CreateDefault(uri);
            //request.PreAuthenticate = true;
            //request.Credentials = credentials;
            //request.ContentLength = content.Length;
            //request.Method = "PUT";
            //request.Timeout = 600000;
            ////CID 0962 //2011.06.27 //Begin
            //int webTimeout = ConfigUtil.WebTimeout();
            //if (webTimeout >= 0)
            //{
            //    request.Timeout = webTimeout;
            //}
            ////CID 0962 //2011.06.27 //End
            ////InfoJet Service --> InfoBus Modified by Sunny 2013.04.07
            //request.UserAgent = "InfoBus (" + Environment.OSVersion + "; .NET CLR " + Environment.Version + ")";
            //request.Headers.Add("Translate", "F");

            //Stream requestStream = request.GetRequestStream();
            //requestStream.Write(content, 0, content.Length);
            //requestStream.Close();

            ////判断结果.
            //HttpWebResponse response = (HttpWebResponse)request.GetResponse();
            ////CID 0936 //2011.06.02 //Begin
            //HttpStatusCode statusCode = response.StatusCode;
            //response.Close();
            ////CID 0936 //2011.06.02 //End

            //if ((response.StatusCode == HttpStatusCode.OK) || (response.StatusCode == HttpStatusCode.Created))
            //{
            //    //如果提交成功,将loginConnection放入Session.
            //    //这里不应该将loginConnection放在FormSession中,因为loginConnection可以被下一个表单继续使用.
            //    if (form.HttpContext.Session != null)
            //    {
            //        form.HttpContext.Session[davAdapter.Id] = loginConnection;
            //    }
            //    //CID 0936 //2011.06.02 //Begin
            //    if (form.Manifest.Submit != null &&
            //        form.Manifest.Submit.DavAdapter != null &&
            //        form.Manifest.Submit.DavAdapter.Name.Equals(davAdapter.Name))
            //    {
            //        form.JetContext.OnAfterDefaultSubmitEvent(form);
            //    }
            //    //CID 0936 //2011.06.02 //End
            //}
            //else
            //{
            //    //CID 1134 //2012.03.14 //Begin
            //    throw new InfoJetException(MessageUtil.HttpErrorToSubmit(response.StatusCode), "DODSW01");
            //    //CID 1134 //2012.03.14 //End
            //}
            // End Modified by lishuchao 2013.6.25
        }

        /*
            WebClient myclient = new WebClient();
            myclient.UploadFile ("http://localhost/upload/odbc.ini","PUT","e:\\tempODBC.INI");
        */

        //根据DavAdapter定义,获取文件名.
        public static string getFileName(Form form, DataDavAdapter davAdapter)
        {
            string fileName;
            //文件名是个表达式.
            if (davAdapter.FileNameValueType.Equals(DataDavAdapter.Expression))
            {
                //计算出文件名.
                //CID 0921 //2011.05.23 //Begin
                fileName = XPathQuery.QueryDavFileNameValue(form, davAdapter);
                //CID 0921 //2011.05.23 //End
                if (fileName == null)
                {
                    return null;
                }
                else
                {
                    fileName = fileName.Trim();
                    if (fileName.Length <= 0)
                    {
                        return null;
                    }
                    else
                    {
                        if (!fileName.ToLower().EndsWith(".xml"))
                        {
                            fileName = fileName + ".xml";
                        }
                    }
                }
            }
            //否则,文件名是固定的.
            else
            {
                fileName = davAdapter.FileNameValue;
                if (!fileName.ToLower().EndsWith(".xml"))
                {
                    fileName = fileName + ".xml";
                }
            }
            if (fileName == null)
            {
                fileName = "Form.xml";
            }
            return fileName;
        }

        //判断WebDav服务器上是否存在表单.
        private static bool existForm(Uri uri, ICredentials credentials)
        {
            HttpWebResponse response = null;
            try
            {
                HttpWebRequest request = (HttpWebRequest)WebRequest.CreateDefault(uri);
                request.Credentials = credentials;
                request.Method = "PROPFIND";
                request.Timeout = 600000;
                //InfoJet Service --> InfoBus Modified by Sunny 2013.04.07
                request.UserAgent = "InfoBus (" + Environment.OSVersion + "; .NET CLR " + Environment.Version + ")";
                request.Headers.Add("Depth", "0");
                request.Headers.Add("Translate", "F");

                response = (HttpWebResponse)request.GetResponse();
                return true;
            }
            catch (WebException exception)
            {
                if (exception.Status == WebExceptionStatus.ProtocolError)
                {
                    response = (HttpWebResponse)exception.Response;
                    if (response.StatusCode == HttpStatusCode.NotFound)
                    {
                        return false;
                    }
                }
                //CID 1144 //2012.03.30 //Begin
                throw exception;
                //CID 1144 //2012.03.30 //End
            }
            finally
            {
                if (response != null)
                {
                    response.Close();
                }
            }
        }

    }
}
